//
//  LcPersistenceMeta.m
//  18Birdies
//
//  Created by Lc on 15/3/23.
//  Copyright (c) 2015年 Lc. All rights reserved.
//

#import "LcJson.h"
#import "LcPersistenceException.h"
#import "LcPersistenceMeta.h"
#import "LcReflection.h"

@implementation LcPersistenceMeta

- (instancetype)initWithFileName:(NSString*)fileName
                            type:(NSString*)type
                    genericTypes:(NSArray*)genericTypes
                     compressing:(BOOL)compressing
                      encrypting:(BOOL)encrypting {
  self = [super init];
  if (self) {
    _fileName = fileName.copy;
    _type = type.copy;
    _genericTypes = genericTypes.copy;
    _compressing = compressing;
    _encrypting = encrypting;
  }
  return self;
}

+ (LcPersistenceMeta*)persistenceMetaWithFileName:(NSString*)fileName
                                             type:(NSString*)type {
  return [self persistenceMetaWithFileName:fileName
                                      type:type
                               compressing:NO
                                encrypting:NO];
}

+ (LcPersistenceMeta*)persistenceMetaWithFileName:(NSString*)fileName
                                             type:(NSString*)type
                                      compressing:(BOOL)compressing
                                       encrypting:(BOOL)encrypting {
  return [self persistenceMetaWithFileName:fileName
                                      type:type
                              genericTypes:nil
                               compressing:compressing
                                encrypting:encrypting];
}

+ (LcPersistenceMeta*)persistenceMetaWithFileName:(NSString*)fileName
                                             type:(NSString*)type
                                     genericTypes:(NSArray*)genericTypes
                                      compressing:(BOOL)compressing
                                       encrypting:(BOOL)encrypting {
  if ([LcReflection isPrimitiveType:type]) {
    @throw [LcPersistenceException
        exceptionWithReason:@"persistence meta cannot be primitive types, "
                            @"please wrap it by an objc class"];
  } else if ([LcReflection isType:type KindOfClass:NSString.class]) {
    @throw [LcPersistenceException
        exceptionWithReason:@"persistence meta cannot be string, "
                            @"please wrap it by an objc class"];
  } else if ([LcReflection isProtocol:type]) {
    @throw [LcPersistenceException
        exceptionWithReason:@"persistence meta cannot be protocol types, "
                            @"please wrap it by an objc class"];
  }
  if ([LcReflection isCollectionType:type]) {
    if (genericTypes.count == 0) {
      @throw [LcPersistenceException
          exceptionWithReason:
              @"genericTypes cannot be empty for collection types"];
    }
  }
  Class clazz = NSClassFromString(type);
  if (clazz == NULL) {
    @throw [LcPersistenceException
        exceptionWithReason:[NSString
                                stringWithFormat:@"unknown type %@", type]];
  }
  return [[self alloc] initWithFileName:fileName
                                   type:type
                           genericTypes:genericTypes
                            compressing:compressing
                             encrypting:encrypting];
}

@end
